home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Experimental BBS Explossion 3
/
Experimental BBS Explossion III.iso
/
gus
/
sdkdigv2.zip
/
SDKV2N10.TXT
next >
Wrap
Text File
|
1993-06-23
|
8KB
|
247 lines
GUS Programmer's Digest Sat Jun 12 00:07 Volume 2: Issue 10
Today's Topics:
Double buffering algorithm
Looping and wave table generation problems
Turbo Pascal SDK alpha release.
Standard Info:
- Meta-info about the GUS can be found at the end of the Digest.
- Before you ask a question, please READ THE FAQ.
----------------------------------------------------------------------
Date: Fri, 11 Jun 93 10:13:21 EST
From: support@fortech.com (Technical Support)
Subject: Double buffering algorithm
Message-ID: <9306111013.0.UUL1.3#16204@fortech.com>
Hi folks,
I've been watching the postings the last few days on how to implement a
double buffering scheme of playing digital audio in the GUS. It is actually
quite simple, but I guess I didn't explain it very well in the SDK.
I'll give a brief description here and I'll try and work up a simple
example over the weekend. (no promises, I'm kinda busy ....)
I'll use small numbers for illustrative pruposes. Your buffers would
normally be much larger. (This example doesn't worry about start up
conditions like not enough data to fill buffers, or exactly what happens at
the end when you run out of data.)
1) Probe for card
2) Open Card.
3) Allocate a chunk of DRAM. Lets say it ends up at locations 1000 to 2000.
4) Allocate a voice (assume mono. stereo just confuses the issue)
5) Set up a callback for wave table IRQ's
6) Read in 1000 bytes of data and send it to the card.
7) Start up the voice with looping on, uni-directional, irqs enabled with the
begin = 1000, start = 1000 and end = 1500. Also turn on the rollover bit
on the volume control register for this voice. This setup will start the
voice up and will generate an IRQ at location 1500. However, the voice
will NOT loop yet. The rollover bit takes precedence.
8) Wait until your foreground code is told it can load a buffer. (See how the
callback is defined below.
9) If filling buffer 0, load 500 bytes into 1000-1500.
If filling buffer 1, load 500 bytes into 1500-2000.
10) Goto step #8 till data is gone.
11) Stop voice
Free memory.
Free Voice.
Close card.
CALLBACK
========
1) If you just played buffer 0 (1000-1500), turn OFF the rollover bit and
set the voice end address to 2000. (This is so when the voice hits 2000, it
will loop back to 1000 and generate an IRQ.) Also tell the foreground that
the first buffer can now be filled with new data (1000-1500). This might
be done by setting a flag that the foreground checks.
If you just played buffer 1 (1500-2000), turn ON the rollover bit and set
set the voice end address to 1500. (This is so when the voice hits 1500,
it will generate and IRQ and continue without looping) Also tell the
forground that the second buffer can now be filled with new data (1500-2000).
This might be done by setting a flag that the forground checks.
===============================================================================
Thats about all there is to it. I've left out some the the implementation
details, but thats the basic flow of the logic.
The above method is useful if you have some control over how much data you
are going to get and when you can get it. If the data is coming to you is
random in length and is under some other applications control, some other
considerations come into play. I don't have time to give an example of it
right now, but it mainly has to do with tacking the data onto the end of
data that is playing and moving the end address to the end of the new data.
When you hit the end of the allocated DRAM buffer, send as much data as you can
to fill the buffer and turn on the loop bit with IRQ. Send the remaining data
down to the beginning of the buffer. When the IRQ comes in, turn the looping off
and set the new end address to the end of the remaining data that you put
at the beginning of the buffer. Sounds complex, but really isn't too bad.
Gotta go get some work done. Hope this helps. Like I said, I'll try and work
up a simple example, but I can't promise it'll be done over the weekend.
Forte Tech. Support.
------------------------------
Date: Fri, 11 Jun 93 12:20:43 EDT
From: davidm@opl.com
Subject: Looping and wave table generation problems
Message-ID: <AFC480DC-80DD0001@woodstock.opl.com>
Hi, GUS Programmers,
I have writen a simple program that downloads a sine wave with varying
amplitude to the GUS' DRAM and then plays it. I have been experimenting
with looping and wave table IRQ generation/handling. It's pretty straight
forward stuff.
The problem I have is that when I enable wave table IRQ's, I get one IRQ,
but no looping even though looping is enabled. This is true with either
uni-directional or bi-directional looping. Am I doing something wrong
(likely) or is this a bug in the SDK (not likely). BTW, I am using the low
level SDK version 2.01.
Below I have included the relevant parts of my program. If it is
compiled with USEIRQS defined, it plays the wave once and stops and one
audible bell character is heard. If it is compiled without USEIRQS defined,
everything works exactly as expected (i.e. the wave loops until a key is
pressed).
This is very puzzling to me. If anyone has any thoughts about what is going
on here, I would love to hear them.
Thanks,
Dave
David MacMahon
Systems Administrator
davidm@opl.com
---------------------
// VOIce Control Bits (from appendix C of LOWSRC.DOC v2.01)
#define VOICB_8BIT 0
#define VOICB_16BIT 4
#define VOICB_NOLOOP 0
#define VOICB_LOOP 8
#define VOICB_UNIDIR 0
#define VOICB_BIDIR 16
#define VOICB_NOWTIRQ 0
#define VOICB_WTIRQ 32
// Global variable
int irqcount;
void HandleWave( int voice_num)
{
irqcount++;
}
void main()
{
.
. [initialization, wave generation and download code deleted]
.
// Grab the wave handler
OldWaveHandler = UltraWaveHandler( HandleWave);
#ifdef USEIRQS
LoopType = VOICB_LOOP | VOICB_UNIDIR | VOICB_WTIRQ;
#else
LoopType = VOICB_LOOP | VOICB_UNIDIR | VOICB_NOWTIRQ;
#endif
// Start voice
UltraStartVoice(
voice_num,
Begin,
Start,
End,
VOICB_8BIT | LoopType);
// Wait
printf( "Playing... Press any key to quit.");
while( !kbhit())
{
if( irqcount)
{
// If there have been wave table IRQ's,
// beep PC speaker and reset IRQ counter
printf("\a");
irqcount = 0;
}
}
.
. [clean-up code deleted]
.
}
------------------------------
Date: Fri, 11 Jun 93 15:00 EDT
From: "Matthew E. Bernold" <MEB117@PSUVM.PSU.EDU>
Subject: Turbo Pascal SDK alpha release.
Message-ID: <9306111859.AA13489@orca.es.com>
Is anyone out there interested in a Pascal translation of the SDK? I have
succeeded in translating about half of the SDK directly from C to Pascal,
and am looking for some testers. If you are interested, please E-mail me
directly. Once I get all the functions translated, I will release a full
beta version on Epas, but for now, I'd like to try a limited distribution.
Also, I'm having a few difficulties in some of the translation problems.
If anyone out there is fluent in both C and Pascal, and has experience with
interrupt handlers and DMA stuff, please drop me a line so I can ask a few
questions and get this thing finished.
Matthew E. Bernold MEB117@PSUVM.PSU.EDU
<<APOCALYPSE>> meb@wilbur.cac.psu.edu
------------------------------
End of GUS Programmer's Digest V2 #10
*************************************
To post to tomorrow's digest: <gus-sdk%itchy@dsd.es.com>
To (un)subscribe or get help: <gus-sdk-request%itchy@dsd.es.com>
To contact a human (last resort): <gus-sdk-owner%itchy@dsd.es.com>
FTP sites: archive.epas.utoronto.ca pub/pc/ultrasound
wuarchive.wustl.edu systems/msdos/ultrasound
Hints:
- Get the FAQ from the FTP sites or the request server.
- Mail to <gus-sdk-request%itchy@dsd.es.com> for info about
other GUS related mailing lists (UNIX, OS/2, GUS-MIDI, etc.)